package com.sand.service.Impl;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.sand.Exception.SandException;
import com.sand.dto.Owner.signSelect;
import com.sand.dto.supplier.PurchaseAll;
import com.sand.entity.buy.detail;
import com.sand.entity.buy.scheme;
import com.sand.entity.conclude.contract;
import com.sand.entity.inventory.SelectInventory;
import com.sand.entity.inventory.inventory;
import com.sand.entity.sell.PurchaseDetail;
import com.sand.entity.shopping.shopping;
import com.sand.feign.*;
import com.sand.mapper.InventoryMapper;
import com.sand.merchant.Permission;
import com.sand.result.AppHttpCodeEnum;
import com.sand.result.ResponseResult;
import com.sand.service.InventoryService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.util.ArrayList;
import java.util.List;

@Service
public class InventoryServiceImpl extends ServiceImpl<InventoryMapper, inventory> implements InventoryService {


    @Autowired
    private merchantFeign merchantFeign;
    
    @Autowired
    private shoppingFeign shoppingFeign;

    @Autowired
    private PurchaseFeign purchaseFeign;

    @Autowired
    private OwnerFeign ownerFeign;

    /**
     * 根据条件查询库存查询库存
     *
     * @param selectInventory
     * @return
     */
    @Override
    public List<inventory> getList(SelectInventory selectInventory) {

        //参数校验
        if (selectInventory.getCid() == null){
            throw new SandException(AppHttpCodeEnum.PARAM_INVALID,"为传入当前操作人id");
        }

        if (selectInventory.getPage() == null || selectInventory.getPageSize() == null){
            throw new SandException(AppHttpCodeEnum.PARAM_INVALID,"为传入要查询页码或页码数");
        }

        Page<inventory> page = new Page<>(selectInventory.getPage(),selectInventory.getPageSize());

        //操作人权限判断
        Integer cid = selectInventory.getCid();

        Integer i = merchantFeign.permission(cid).getData();
        
        if (i == null || i.equals(Permission.NO)){
            throw new SandException(AppHttpCodeEnum.PARAM_INVALID,"权限不够无法查询库存");
        }

        //表达式
        LambdaQueryWrapper<inventory> wrapper = new LambdaQueryWrapper<>();

        //返回数据的集合
        List<inventory> list = new ArrayList<>();


        if (selectInventory.getShoppingId() != null){
            //判断商品是否存在
            shopping shopping = shoppingFeign.select(selectInventory.getShoppingId()).getData();

            if (shopping == null){
                throw new SandException(AppHttpCodeEnum.PARAM_INVALID,"传入的商品id不存在");
            }

            inventory one = getOne(wrapper.eq(inventory::getShoppingId, selectInventory.getShoppingId()));

            list.add(one);

            return list;
        }

        //查询库存不足数量的
        if (selectInventory.getAmount() != null){
            wrapper.le(inventory::getAmount,selectInventory.getAmount());
        }

        return page(page, wrapper).getRecords();
    }



    /**
     * 查询某个商品拼的库存
     *
     * @param shoppingid
     */
    @Override
    public inventory get(Integer shoppingid) {

        //判断商品是否存在
        shopping shopping = shoppingFeign.getO(shoppingid).getData();

        if (shopping == null){
            throw new SandException(AppHttpCodeEnum.PARAM_INVALID,"该商品不存在");
        }

        LambdaQueryWrapper<inventory> wrapper = new LambdaQueryWrapper<>();

        wrapper.eq(inventory::getShoppingId,shopping.getId());

        return getOne(wrapper);
    }


    /**
     * 新增库存
     *
     * @param i
     */
    @Override
    public Integer add(inventory i) {

        i.setId(null);

        Integer shoppingId = i.getShoppingId();

        Integer amount = i.getAmount();

        if (shoppingId == null){
            throw new SandException(AppHttpCodeEnum.PARAM_INVALID,"没有传入添加的商品id");
        }

        shopping shopping = shoppingFeign.getO(shoppingId).getData();

        if (shopping == null){
            throw new SandException(AppHttpCodeEnum.PARAM_INVALID,"添加的商品不存在");
        }

        if (amount == null){
            throw new SandException(AppHttpCodeEnum.PARAM_INVALID,"没有传入要添加的商品库存的数量");
        }

        inventory one = getOne(new LambdaQueryWrapper<inventory>().eq(inventory::getShoppingId, shoppingId));

        if (one == null){
            //添加
            save(i);
        }else {
            //库存加
            one.setAmount(one.getAmount()+i.getAmount());

            updateById(one);
        }

        return 1;
    }

    /**
     * 完成采购新增库存
     *
     * @param purchaseid
     */
    @Override
    @Transactional
    public Integer addlist(Integer purchaseid) {

        if (purchaseid == null){
            throw new SandException(AppHttpCodeEnum.PARAM_INVALID,"没有传入采购单");
        }

        //根据采购单获取详细
        PurchaseAll purchaseAll = purchaseFeign.all(purchaseid).getData();

        if (purchaseAll == null){
            throw new SandException(AppHttpCodeEnum.PARAM_INVALID,"该采购单不存在");
        }

        //获取订购单的商品
        PurchaseDetail[] arr = purchaseAll.getArr();

        ArrayList<inventory> arrayList = new ArrayList<>();

        for (PurchaseDetail purchaseDetail : arr) {
            Integer shoppingid = purchaseDetail.getShoppingid();
            Integer amount = purchaseDetail.getAmount();

            inventory one = getOne(new LambdaQueryWrapper<inventory>().eq(inventory::getShoppingId, shoppingid));

            if (one == null) {
                throw new SandException(AppHttpCodeEnum.PARAM_INVALID,"添加了不存在的商品");
            }

            //新增数量
            one.setAmount(one.getAmount() + amount);

            arrayList.add(one);

        }

        //添加库存
        saveBatch(arrayList);

        return 1;
    }

    /**
     * 根据合同扣减库存
     *
     * @param contractid
     */
    @Override
    @Transactional
    public Integer subtract(Integer contractid) {

        //根据合同获取方案id
        contract contract = merchantFeign.get(contractid).getData();

        //根据方案获取明细
        scheme scheme = ownerFeign.getid(contract.getSchemeid()).getData();

        //根据明细获取标记
        detail detail = ownerFeign.getByid(scheme.getDetailid()).getData();

        //根据标记获取商品
        List<signSelect> data = ownerFeign.select(detail.getSign()).getData();

        ArrayList<inventory> list = new ArrayList<>();

        for (signSelect datum : data) {

            inventory inventory = getById(datum.getId());

            if (inventory == null){
                throw new SandException(AppHttpCodeEnum.PARAM_INVALID,"传入的商品有误");
            }

            if (datum.getAmount() > inventory.getAmount()){
                throw new SandException(AppHttpCodeEnum.PARAM_INVALID,"库存不够无法扣减");
            }

            inventory.setAmount(inventory.getAmount() - datum.getAmount());

            list.add(inventory);
        }

        updateBatchById(list);

        return 1;
    }


}
